home *** CD-ROM | disk | FTP | other *** search
/ Night Owl 6 / Night Owl's Shareware - PDSI-006 - Night Owl Corp (1990).iso / 001a / jmod310.zip / JMODEM_F.C < prev    next >
Text File  |  1991-11-30  |  24KB  |  499 lines

  1. /****************************************************************************/
  2. /*   FILE JMODEM_F.C                                                        */
  3. /*   Created 11-JAN-1990                    Richard B. Johnson              */
  4. /*                                          405 Broughton Drive             */
  5. /*                                          Beverly, Massachusetts 01925    */
  6. /*                                          BBS (508) 922-3166              */
  7. /*                                                                          */
  8. /*   screen();         All screen output procedures. Uses INT 10H under     */
  9. /*                     MS-DOS.                                              */
  10. /*                                                                          */
  11. /*   disp();           Displays a "USAGE" message                           */
  12. /*                                                                          */
  13. /*   These routines are absolutely not necessary and could be replaced      */
  14. /*   with _printf() statements. They are used to make the pretty screens    */
  15. /*   and overlapping windows that the PC community has grown to expect.     */
  16. /*                                                                          */
  17. /****************************************************************************/
  18. #define  SCREEN                                  /* For var len param list  */
  19. #include <stdio.h>
  20. #include <dos.h> 
  21. #include <stdlib.h>
  22. #include <string.h>
  23. #include "screen.h"
  24. #include "jmodem.h"
  25. #if defined (TURBOC)
  26.     #include <alloc.h>
  27. #else
  28.     #include <malloc.h>                           /* Used for _malloc();   */
  29. #endif
  30. short sav_par[BOXES * PARAM];                     /* Save row/columns       */
  31. short *buffer[BOXES];                             /* Pointers for  boxes    */
  32. short last_box = 0;                               /* Last box on the screen */
  33. short start_txt;                                  /* Text starts in box     */
  34. short start_row;                                  /* Starting row of box    */
  35. short start_col;                                  /* Starting column of box */
  36. short end_row;                                    /* Ending row of box      */
  37. short end_col;                                    /* Ending column of box   */
  38.  
  39. byte abrt[]  = "Aborted!";                        /* Five status messages   */
  40. byte okay[]  = "Okay ";
  41. byte retry[] = "Retry";
  42. byte done[]  = "Done!";
  43. byte flow[]  = "Flow ";
  44.  
  45. char info[] = "Usage:\r\n"\
  46.               "JMODEM R1 filename\r\n"\
  47.               "       ||___ COM port (1..4)\r\n"\
  48.               "       |____ [R]eceive, [S]end\r\n"
  49.               " - or -\r\n"
  50.               "JMODEM R(3F8:4) filename\r\n"
  51.               "       |   | |___ IRQ to use (1..7)\r\n"
  52.               "       |   |_____ absolute port address (hex) \r\n"
  53.               "       |_________ [R]eceive, [S]end\r\n";
  54.  
  55. byte malfail[] = "Memory allocation failed!";
  56.  
  57. char *signon[] = {
  58.                  "     J M O D E M",
  59.                  "File transfer protocol",
  60.                  "     "VERS
  61.                  };
  62.  
  63. char *sta_blk[] = {
  64.                   "   Block :" ,
  65.                   "  Length :" ,
  66.                   "   Bytes :" ,
  67.                   "Rate CPS :" ,
  68.                   "  Status :" ,
  69.                   "Synchronizing ...", 
  70.                   "  Receiving file ",
  71.                   "Transmitting file"
  72.                   };
  73.  
  74. char *fil_blk[] = {
  75.                   "Opening file ",
  76.                   "Can't open the file!",
  77.                   "Open okay",
  78.                   "File exists, renaming to ",
  79.                   "Can't create the file!",
  80.                   };
  81. /****************************************************************************/
  82. /*                                C O D E                                   */
  83. /****************************************************************************/
  84. void screen (short function, SYS *sys)
  85. {
  86.     union REGS bios;                              /* For int 10H            */
  87.     register const ATTRIB *attr;                  /* For attribute table    */
  88.     register const short *index;                  /* Array pointer          */
  89.     short page;                                   /* Box number             */
  90.     short i;
  91.  
  92.     bios.x.ax =                                   /* Initialize             */
  93.     bios.x.bx =
  94.     bios.x.cx =
  95.     bios.x.dx = 0;
  96.  
  97.     attr = attribute + last_box;                  /* Default attribute      */
  98.     switch (function)
  99.     {
  100.         case SCR_SGN:                             /* Sign-on message        */
  101.         {
  102.             page=0;                               /* Box number             */
  103.             kill_curs(&bios);
  104.             attr      = attribute + page;
  105.             index     = box_loc + (page * BOXES);
  106.             start_row = *index++;
  107.             start_col = *index++;
  108.             end_row   = *index++;
  109.             end_col   = *index;
  110.             start_txt = start_row + 1;
  111.             set_box (page     ,                   /* Page                   */
  112.                      attr->win,                   /* Screen attribute       */
  113.                      start_row,                   /* Start row              */
  114.                      start_col,                   /* Start column           */
  115.                      end_row  ,                   /* End row                */
  116.                      end_col  ,                   /* End column             */
  117.                      sav_par  ,
  118.                      buffer   ,
  119.                      &bios  );
  120.             for (i = 0; i<3; i++)
  121.             {
  122.                 set_curs (start_txt++,start_col + 4,&bios);
  123.                 write_str(signon[i],attr->txt,&bios);
  124.             }
  125.             last_box = page;
  126.             break;
  127.         }
  128.     case SCR_FIL:                                 /* File screen            */
  129.         {
  130.             page=1;
  131.             attr      = attribute + page;
  132.             index     = box_loc + (page * BOXES);
  133.             start_row = *index++;
  134.             start_col = *index++;
  135.             end_row   = *index++;
  136.             end_col   = *index;
  137.             start_txt = start_row + 1;
  138.             set_box (page     ,                   /* Page                   */
  139.                      attr->win,                   /* Screen attribute       */
  140.                      start_row,                   /* Start row              */
  141.                      start_col,                   /* Start column           */
  142.                      end_row  ,                   /* End row                */
  143.                      end_col  ,                   /* End column             */
  144.                      sav_par  ,
  145.                      buffer   ,
  146.                      &bios  );
  147.             set_curs (start_txt++,start_col + 3,&bios);
  148.             write_str(fil_blk[0],attr->txt,&bios);
  149.             write_str(sys->s_txt,attr->txt,&bios);
  150.             last_box=page;
  151.             break;
  152.         }
  153.     case SCR_FNF:                                 /* File not found         */
  154.         {
  155.             set_curs (start_txt++ ,start_col + 3, &bios);
  156.             write_str(fil_blk[1],attr->txt,&bios);
  157.             break;
  158.         }
  159.     case SCR_FOK:                                 /* File found okay        */
  160.         {
  161.             set_curs (start_txt++, start_col + 3, &bios);
  162.             write_str(fil_blk[2],attr->txt,&bios);
  163.             if (sys)
  164.             {
  165.                 strcpy(info,"File size = ");
  166.                 ltoa (sys->s_byt,&info[12],10);
  167.                 set_curs (start_txt-1, start_col + 38, &bios);
  168.                 write_str(info,attr->txt,&bios);
  169.             }
  170.             break;
  171.         }
  172.     case SCR_STA:                                 /* Status block           */
  173.         {
  174.             page      = 2;
  175.             attr      = attribute + page;
  176.             index     = box_loc + (page * BOXES);
  177.             start_row = *index++;
  178.             start_col = *index++;
  179.             end_row   = *index++;
  180.             end_col   = *index;
  181.             start_txt = start_row + 1;
  182.             set_box (page     ,                   /* Page                   */
  183.                      attr->win,                   /* Screen attribute       */
  184.                      start_row,                   /* Start row              */
  185.                      start_col,                   /* Start column           */
  186.                      end_row  ,                   /* End row                */
  187.                      end_col  ,                   /* End column             */
  188.                      sav_par  ,
  189.                      buffer   ,
  190.                      &bios  );
  191.  
  192.             for (i=0; i<6; i++)
  193.             {
  194.                 set_curs (start_txt+i,start_col + 4,&bios);
  195.                 write_str(sta_blk[i],attr->txt,&bios);
  196.             }
  197.             last_box = page;
  198.             break;
  199.         }
  200.    case SCR_FRN:                                  /* File renamed           */
  201.         {
  202.             set_curs (start_txt++, start_col + 3, &bios);
  203.             write_str(fil_blk[3],attr->txt,&bios);
  204.             write_str(sys->s_txt,attr->txt,&bios);
  205.             break;
  206.         }
  207.    case SCR_FCR:                                  /* File created           */
  208.         {
  209.             set_curs (start_txt++, start_col + 3, &bios);
  210.             write_str(fil_blk[4],attr->txt,&bios);
  211.             break;
  212.         }
  213.    case SCR_SYR:                                  /* Sync receive           */
  214.         {
  215.             start_txt = start_row + 1;
  216.             set_curs (start_txt + 5, start_col + 4, &bios);
  217.             write_str(sta_blk[6],attr->txt | 0x8000 ,&bios);
  218.             break;
  219.         }
  220.    case SCR_SYT:                                  /* Sync transmit          */
  221.         {
  222.             start_txt = start_row + 1;
  223.             set_curs (start_txt + 5, start_col + 4, &bios);
  224.             write_str(sta_blk[7],attr->txt | 0x8000,&bios);
  225.             break;
  226.         }
  227.     case SCR_SYS:
  228.         {
  229.             itoa(sys->s_blk,info,10);             /* Block number           */
  230.             set_curs (start_txt, start_col + 15, &bios);
  231.             write_str(info,attr->txt, &bios);     /* Write string to screen */
  232.             memset(info,0x20,0x08);               /* Fixed length string    */
  233.             info[0x07] = 0x00;                    /* Set a null             */
  234.             itoa(sys->s_len,info,10);             /* Block length           */
  235.             *(strchr(info,0x00)) = 0x20;          /* Fill in the NULL       */
  236.             set_curs (start_txt + 1, start_col + 15, &bios);
  237.             write_str(info,attr->txt, &bios);
  238.             ltoa(sys->s_byt,info,10);             /* Total bytes            */
  239.             set_curs (start_txt + 2, start_col + 15, &bios);
  240.             write_str(info,attr->txt, &bios);     /* Write string to screen */
  241.             memset(info,0x20,0x08);               /* Fixed length string    */
  242.             info[0x07] = 0x00;                    /* Set a null             */
  243.             itoa(sys->s_cps,info,10);             /* Speed, cps             */
  244.             *(strchr(info,0x00)) = 0x20;          /* Fill in the NULL       */
  245.             set_curs (start_txt + 3, start_col + 15, &bios);
  246.             write_str(info,attr->txt, &bios);
  247.         }                                         /* Fall through, no break */
  248.     case SCR_FLG:
  249.         {
  250.             set_curs (start_txt + 4, start_col + 15, &bios);
  251.             write_str(sys->s_sta,attr->txt, &bios);
  252.             break;
  253.         }
  254.     case SCR_END:
  255.         {
  256.             do
  257.             {
  258.                 end_box (last_box, sav_par, buffer, &bios);
  259.             }   while (last_box--);
  260.             restore_curs(&bios);
  261.             break;
  262.         }
  263.     }
  264.     return;
  265. }
  266. /****************************************************************************/
  267. /*  Save screen contents in a buffer obtained from _malloc. Write a border  */
  268. /*  and screen attributes to saved screen location.  Record the address of  */
  269. /*  the buffer so the screen contents may be restored. Global *buffer[] is  */
  270. /*  used to save the pointers.                                              */
  271. /****************************************************************************/
  272. void set_box (short page ,                        /* Box number             */
  273.              word screen,                         /* Screen attribute       */
  274.              short start_row,                     /* Start row of border    */
  275.              short start_col,                     /* Start column of border */
  276.              short end_row,                       /* End row of border      */
  277.              short end_col,                       /* End column of border   */
  278.              register short *sav_par,
  279.              register short *buffer[],
  280.              union REGS *bios)
  281. {
  282.     word putscr;
  283.     short sav_col;
  284.     short sav_row;
  285.     short row;
  286.     short col;
  287.     short memory;
  288.  
  289.     memory  = (end_row - start_row);
  290.     memory *= (end_col - start_col);
  291.     memory *= sizeof (short);
  292.     buffer[page] = (short *) malloc(memory);      /* Get pointer to memory  */
  293.     if (!buffer[page])
  294.         return;
  295.  
  296.     get_curs(bios);                               /* Get cursor position    */
  297.     sav_row    = (short) bios->h.dh;              /* Save cursor row        */
  298.     sav_col    = (short) bios->h.dl;              /* Save cursor column     */
  299.     sav_par   += (page * PARAM);                  /* Calculate index once   */
  300.     *sav_par++ = screen;
  301.     *sav_par++ = start_row;
  302.     *sav_par++ = start_col;
  303.     *sav_par++ = end_row;
  304.     *sav_par++ = end_col;
  305.     *sav_par++ = sav_row;
  306.     *sav_par   = sav_col;
  307.  
  308.     for (row = start_row; row < end_row; row++)
  309.     {
  310.         for (col = start_col; col < end_col; col++)
  311.         {
  312.             set_curs (row,col,bios);                   /* Set cursor pos    */
  313.             *buffer[page]++ = get_char_atr(bios);      /* Save char/attr    */
  314.             putscr = screen | 0x20;                    /* default (else)    */
  315.             if (row == start_row || row == end_row-1)  /* Top and bottom    */
  316.                 putscr = screen | 205;
  317.             if (col == start_col || col == end_col-1)  /* Right and left    */
  318.                 putscr = screen | 186;
  319.             if (row == start_row && col == start_col)  /* NW corner         */
  320.                 putscr = screen | 201;
  321.             if (row == start_row && col == end_col-1)  /* NE corner         */
  322.                 putscr = screen | 187;
  323.             if (row == end_row-1 && col == start_col)  /* SW corner         */
  324.                 putscr = screen | 200;
  325.             if (row == end_row -1 && col == end_col-1) /* SE corner         */
  326.                 putscr = screen | 188;
  327.             set_char_atr (putscr,bios);                /* Write to screen   */
  328.         }
  329.     }
  330.     return;
  331. }
  332. /****************************************************************************/
  333. /*  Restore the screen contents saved in memory pointed to by *buffer[].    */
  334. /****************************************************************************/
  335. void end_box (short page,
  336.               register short *sav_par,
  337.               register short *buffer[],
  338.               union REGS  *bios)
  339. {
  340.     short start_row;
  341.     short start_col;
  342.     short end_row;
  343.     short end_col;
  344.     short row;
  345.     short col;
  346.     short sav_row;
  347.     short sav_col;
  348.  
  349.     sav_par  += (page * PARAM);                   /* Calculate index once   */
  350.     sav_par++;                                    /* Bypass screen entry    */
  351.     start_row = *sav_par++;
  352.     start_col = *sav_par++;
  353.     end_row   = *sav_par++;
  354.     end_col   = *sav_par++;
  355.     sav_row   = *sav_par++;
  356.     sav_col   = *sav_par;
  357.  
  358.     buffer[page] -= ( (end_row - start_row)       /* Get buffer start       */
  359.                * (end_col - start_col) );
  360.  
  361.     for (row = start_row; row < end_row; row++)
  362.     {
  363.         for (col = start_col; col < end_col; col++)
  364.         {
  365.             set_curs (row,col,bios);              /* Set cursor pos         */
  366.             set_char_atr(*buffer[page]++,bios);   /* Restore screen         */
  367.         }
  368.     }
  369.     free(buffer[page]);                           /* Free allocated memory  */
  370.     set_curs (sav_row,sav_col,bios);              /* Restore cursor         */
  371.     return;
  372. }
  373. /****************************************************************************/
  374. /*                      Set Cursor to row, column                           */
  375. /****************************************************************************/
  376. void set_curs (short row, short col, register union REGS *bios)
  377. {
  378.     bios->h.ah=(byte) 0x02;                       /* Set cursor function    */
  379.     bios->h.dh=(byte) row;                        /* Row                    */
  380.     bios->h.dl=(byte) col;                        /* Column                 */
  381.     bios->h.bh=(byte) 0x00;                       /* Page 0                 */
  382.     int86(VIDEO, bios, bios);                     /* Use for in and out     */
  383.     return;
  384. }
  385. /****************************************************************************/
  386. /*                          Get the cursor position                         */
  387. /****************************************************************************/
  388. void get_curs(register union REGS *bios)
  389. {
  390.     bios->h.ah=(byte) 0x03;                       /* Get cursor function    */
  391.     bios->h.bh=(byte) 0x00;                       /* Page 0                 */
  392.     int86(VIDEO, bios, bios);                     /* Use for in and out     */
  393.     return;
  394. }
  395. /****************************************************************************/
  396. /*                           Turn off the cursor                            */
  397. /****************************************************************************/
  398. void kill_curs(register union REGS *bios)
  399. {
  400.     bios->h.ah=(byte) 0x01;                       /* Set cursor function    */
  401.     bios->h.bh=(byte) 0x00;                       /* Page 0                 */
  402.     bios->x.cx=(word) 0xFFFF;                     /* Kill the cursor        */
  403.     int86(VIDEO, bios, bios);                     /* Use for in and out     */
  404.     return;
  405. }
  406. /****************************************************************************/
  407. /*                         Restore the cursor type                          */
  408. /****************************************************************************/
  409. void restore_curs(register union REGS *bios)
  410. {
  411.     bios->h.ah=(byte) 0x01;                       /* Get cursor function    */
  412.     bios->h.bh=(byte) 0x00;                       /* Page 0                 */
  413.     bios->x.cx=(word) 0x0607;                     /* Restore the cursor     */
  414.     int86(VIDEO, bios, bios);                     /* Use for in and out     */
  415.     return;
  416. }
  417. /****************************************************************************/
  418. /*                    Write char /attr at cursor position                   */
  419. /****************************************************************************/
  420. void set_char_atr(word atr_chr, register union REGS *bios)
  421. {
  422.     bios->h.ah=(byte) 0x09;                       /* Write char function    */
  423.     bios->h.al=(byte) atr_chr;                    /* Character              */
  424.     bios->h.bl=(byte) (atr_chr >> 8);             /* Attribute              */
  425.     bios->h.bh=(byte) 0x00;                       /* Page 0                 */
  426.     bios->x.cx=1;                                 /* One character          */
  427.     int86(VIDEO, bios, bios);                     /* Use for in and out     */
  428.     return;
  429. }
  430. /****************************************************************************/
  431. /*                   Get char /attr at cursor position                      */
  432. /****************************************************************************/
  433. word get_char_atr(register union REGS *bios)
  434. {
  435.     bios->h.ah=(byte) 0x08;                       /* Read char function     */
  436.     bios->h.bh=(byte) 0x00;                       /* Page 0                 */
  437.     int86(VIDEO, bios, bios);                     /* Use for in and out     */
  438.     return (bios->x.ax);                          /* Its in the AX regis    */
  439.  }
  440. /****************************************************************************/
  441. /*         Write a string with attributes at current position               */
  442. /****************************************************************************/
  443. void write_str(register char *string, word atr, register union REGS *bios)
  444. {
  445.     short row;
  446.     short col;
  447.     while (*string)                               /* Until the NULL         */
  448.     {
  449.         set_char_atr(atr|(short)*string++, bios); /* Write char and attr    */
  450.         get_curs(bios);                           /* Get cursor position    */
  451.         row = (short) bios->h.dh;                 /* Get row                */
  452.         col = (short) bios->h.dl;                 /* Get column             */
  453.         if (col > 69)                             /* Protect window         */
  454.             break;
  455.         set_curs (row,++col,bios);                /* Set column             */
  456.     }
  457.     return;
  458. }
  459. /****************************************************************************/
  460. /*    Substitutes for the enormous _puts (char *) runtime module            */
  461. /*                                                                          */
  462. /****************************************************************************/
  463. int puts(register const char *string)
  464. {
  465.     union REGS bios;
  466.     while (*string)
  467.     {
  468.         bios.h.al=(byte) *string++;               /* Character to print     */
  469.         bios.h.ah=(byte) 0x0E;                    /* Dumb terminal function */
  470.         bios.h.bh=(byte) 0x00;                    /* Page 0                 */
  471.         int86(VIDEO, &bios, &bios);               /* Use for in and out     */
  472.     }
  473.     bios.h.al=(byte) 0x0D;                        /* Character to print     */
  474.     bios.h.ah=(byte) 0x0E;                        /* Dumb terminal function */
  475.     bios.h.bh=(byte) 0x00;                        /* Page 0                 */
  476.     int86(VIDEO, &bios, &bios);                   /* Use for in and out     */
  477.  
  478.     bios.h.al=(byte) 0x0A;                        /* Character to print     */
  479.     bios.h.ah=(byte) 0x0E;                        /* Dumb terminal function */
  480.     bios.h.bh=(byte) 0x00;                        /* Page 0                 */
  481.     int86(VIDEO, &bios, &bios);                   /* Use for in and out     */
  482.     return(0);
  483. }
  484. /****************************************************************************/
  485. /*                          Print the 'Usage' prompt.                       */
  486. /*    Made complicated so we don't have to use the ENORMOUS _printf()       */
  487. /*    library file.  This saves a lot of space!                             */
  488. /*                                                                          */
  489. /****************************************************************************/
  490. void disp()
  491. {
  492.     puts(signon[2]);
  493.     puts(info);
  494.     return;
  495. }
  496. /****************************************************************************/
  497. /*                       E N D  O F  M O D U L E                            */
  498. /****************************************************************************/
  499.